#include "GridBinReader.h"

namespace OCPP {
	namespace Volume {
		class CapVariable : public GridVariable
		{
		public:
			CapVariable(String name, CapBinDataReader& dataReader)
				:dataReader(dataReader)
				, name(name)
			{

			}

			String getTimeString(int index)
			{
				int year = dataReader.header.year;
				int month = dataReader.header.month;
				int day = dataReader.header.day;
				int hour = dataReader.header.hour;
				int min = dataReader.header.min;
				int sec = dataReader.header.sec;
				return str_format("%d%02d%02d%02d%02d%02d", year, month, day, hour, min, sec);
			}

			GridShape getShape() { 
				return {
					1,1,(size_t)dataReader.header.nX,(size_t)dataReader.header.nY,
				};
			}
			

			String getUnitsString()
			{
				return dataReader.header.units;
			}

			FloatVector readFloat()
			{
				if (name == "longitude")
				{
					float dx = dataReader.header.dx * 0.1;
					FloatVector fv;
					fv.resize(dataReader.header.nX);
					for (auto i = 0; i < fv.size(); i++)
					{
						fv[i] = (dataReader.header.edge_w + i * dx) * 0.001f;
					}
					return fv;
				}
				if (name == "latitude")
				{
					float dy = dataReader.header.dy * 0.1f;
					FloatVector fv;
					fv.resize(dataReader.header.nY);
					for (auto i = 0; i < fv.size(); i++)
					{
						fv[i] = (dataReader.header.edge_s + i * dy) * 0.001f;
					}
					return fv;
				}
				if (name == "height")
				{
					return {
						(float)dataReader.header.height
					};
				}
				if (name == "time")
				{
					return {
						0
					};
				}

				return FloatVector();
			}

			StringVector getDims() { return { "time", "height", "longitude","latitude" }; }

			String name;
			CapBinDataReader& dataReader;
		};

		bool GridBinReader::open(String fileName)
		{
			ifsStream = std::make_shared<std::ifstream>(fileName, std::ios::binary);

			if (ifsStream->is_open())
			{
				gridDataReaderPtr = std::make_shared<CapBinDataReader>(*ifsStream);
				if (gridDataReaderPtr->hasError)
				{
					gridDataReaderPtr = nullptr;
				}
			}

			return gridDataReaderPtr != nullptr;
		}

		GridVariablePtr GridBinReader::findVariable(String name)
		{
			return std::make_shared<CapVariable>(name, *gridDataReaderPtr);
		}

		GridDataReaderPtr GridBinReader::getDataReader(GridShape origin, GridShape shape, GridVariablePtr variable)
		{
			return gridDataReaderPtr;
		}

	}
}